package lc.com.pcsc.ui;

import android.os.Bundle;
import android.support.v7.app.AppCompatActivity;
import android.util.Log;
import android.view.View;
import android.widget.Button;
import android.widget.EditText;
import android.widget.TextView;
import android.widget.Toast;

import com.example.jin.des.CmdManager;
import com.example.jin.des.Constants;
import com.example.jin.des.DesUtil;

import java.io.DataOutputStream;
import java.util.UUID;

import lc.com.pcsc.LibPcsc;
import lc.com.pcsc.R;
import lc.com.pcsc.model.DataUnit;
import lc.com.pcsc.utils.EncodeUtil;

import static com.example.jin.des.ByteUtil.HexToString;
import static com.example.jin.des.ByteUtil.StringToHex;

public class MainActivity extends AppCompatActivity {
    static private final String TAG = MainActivity.class.getSimpleName();
    private TextView mLogText;

    EditText etCmd;


    private byte[] key = new byte[16];
    private byte[] key1;
    private byte[] key2;

    private int mCurrentSlot = 0;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        etCmd = (EditText) findViewById(R.id.etCmd);

        key1 = getRandomKey(8);


//        try {
//            Runtime.getRuntime().exec("su"); //切换到root帐号
//        } catch (Exception e) {
//            Log.e("Main", "su fail");
//        }
//        if(!UpgradeRootPermission("chmod -R 0666 /dev/bus/usb/*")){
//            Log.d(TAG, "chmod fail");
//        }
        // Example of a call to a native method
        mLogText = (TextView) findViewById(R.id.log_text);

        Button mInitButton = (Button) findViewById(R.id.init_button);
        mInitButton.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
//                if(!UpgradeRootPermission("chmod -R 0666 /dev/bus/usb/*")){
//                    Log.d(TAG, "chmod fail");
//                }
                //int ret = Pcsc.init();
                //UpgradeRootPermission("chmod -R 0666 /dev/bus/usb/*");

                int ret = LibPcsc.init();
                LibPcsc.slotId(0);
                mLogText.setText("初始化成功");
                //Log.d(TAG, "Init return:" + ret);
            }
        });

        Button mDevicesButton = (Button) findViewById(R.id.devices_button);
        mDevicesButton.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                mLogText.setText("Devices");
                if (mCurrentSlot == 0) {
                    mCurrentSlot = 1;
                    mLogText.setText("接触模式");
                } else if (mCurrentSlot == 1) {
                    mCurrentSlot = 2;
                    mLogText.setText("sim卡模式");
                } else {
                    mCurrentSlot = 0;
                    mLogText.setText("非接触模式");
                }
                LibPcsc.slotId(mCurrentSlot);
            }
        });

        Button mConnectButton = (Button) findViewById(R.id.connect_button);
        mConnectButton.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                DataUnit atr = new DataUnit(64);
                int ret = LibPcsc.powerOn("", atr);
                if (ret == 0) {
                    String sAtr = HexToString(atr.data, atr.length);
                    mLogText.setText("连接成功:" + sAtr);
                    Log.d(TAG, "Connect ATR:" + sAtr);
                } else {
                    mLogText.setText("连接失败");
                }
            }
        });

        Button mExchangeButton = (Button) findViewById(R.id.exchange_button);
        mExchangeButton.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                mLogText.setText("");

                byte[] buff = CmdManager.buildExchangeCmd(key1);

                DataUnit sApdu = new DataUnit(buff, buff.length);
                DataUnit rApdu = new DataUnit(256);

                LibPcsc.APDU(sApdu, rApdu);
                mLogText.setText("秘钥交换成功:" + HexToString(rApdu.data, rApdu.length));
                key2 = new byte[8];
                System.arraycopy(rApdu.data, 1, key2, 0, 8);
                try {
//                    byte[] kk = EncodeUtil.des3DecodeECB(Constants.ROOT_KEY, key2);
                    DesUtil.TripleDes_Decryption(key2, Constants.ROOT_KEY);

                } catch (Exception e) {
                    e.printStackTrace();
                }
                key = EncodeUtil.byteContact(key1, key2);
            }
        });

        Button mApduAsciiButton = (Button) findViewById(R.id.apdu_ascii_button);
        mApduAsciiButton.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                String cApdu = etCmd.getText().toString().trim();
                if (cApdu.length() > 0) {
                    //String capdu = new byte[]{0x00, (byte) 0x84, 0x00, 0x00, 0x08};
                    try {
                        String cmd = CmdManager.buildAPDUAsciiCmd(cApdu, key);
                        String rapdu = LibPcsc.APDUAscii(cmd);
                        mLogText.setText("发送成功:" + rapdu);
                        Log.d(TAG, "Resp:" + rapdu);
                    } catch (Exception e) {
                        e.printStackTrace();
                    }
                } else {
                    Toast.makeText(MainActivity.this, "数据不能为空", Toast.LENGTH_SHORT).show();
                }

            }
        });

        Button mDisconnectButton = (Button) findViewById(R.id.disconnect_button);
        mDisconnectButton.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                Log.d(TAG, "Disconnect");
                mLogText.setText("连接已断开");
                LibPcsc.powerOff();
            }
        });

        Button btnBuildGraph = (Button) findViewById(R.id.btn_build_graph);
        btnBuildGraph.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                String content = "00A40000026FF2";
                String strCmd = CmdManager.buildAPDUAsciiCmd(content, key);
                System.out.println("--------->" + strCmd);
                String rapdu = LibPcsc.APDUAscii(strCmd);
                byte[] a = StringToHex(rapdu);
                DesUtil.TripleDes_Decryption(a, key);
                System.out.println("--------->" + rapdu + "---" + HexToString(a));
                String strCmd1 = CmdManager.buildAPDUAsciiCmd("00B0000008", key);
                String b = LibPcsc.APDUAscii(strCmd1);
                byte[] c = StringToHex(b);
                DesUtil.TripleDes_Decryption(c, key);
                System.out.println("--------->" + HexToString(c));

            }
        });

        LibPcsc.init();

        while (true) {
            int ret = LibPcsc.isCardPresent("");
//            Log.d(TAG, "onCreate: 卡状态" + ret);
            try {
                Thread.sleep(1000);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
    }

    /**
     * 获取随机秘钥
     *
     * @param len 获取秘钥长度
     * @return key
     */
    public byte[] getRandomKey(int len) {
        String uuid = UUID.randomUUID().toString().substring(0, len);
        return uuid.getBytes();
    }


    /**
     * 以Root权限执行命令
     *
     * @param cmd 需要以root权限执行的命令
     * @return 是否获取root权限
     */
    public static boolean UpgradeRootPermission(String cmd) {
        Process process = null;
        DataOutputStream os = null;
        try {
            process = Runtime.getRuntime().exec("su"); //切换到root帐号
            os = new DataOutputStream(process.getOutputStream());
            os.writeBytes(cmd + "\n");
            os.writeBytes("exit\n");
            os.flush();
            process.waitFor();
        } catch (Exception e) {
            return false;
        } finally {
            try {
                if (os != null) {
                    os.close();
                }
                assert process != null;
                process.destroy();
            } catch (Exception ignored) {
            }
        }
        return true;
    }


}
